/*
 * Copyright (c) 2009-2013 EvTech Project
 * All rights reserved.
 * 
 * This file is part of LModeller.
 *
 * LModeller is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or 
 * (at your option) any later version.
 *
 * LModeller is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with LModeller.  If not, see <http://www.gnu.org/licenses/>.
 * 
 */
package fi.honkalampisaatio.lmodeller.ui;

import java.awt.Font;

import fi.honkalampisaatio.lmodeller.LModeller;
import fi.honkalampisaatio.lmodeller.sound.VoicePlayer;
import fi.honkalampisaatio.lwjgl.GLTexture;
import fi.honkalampisaatio.lwjgl.TrueTypeFont;
import glapp.GLApp;

import org.lwjgl.opengl.GL11;
import org.lwjgl.util.Rectangle;

public class GameButton extends UIElement  {
	GLTexture texture;
	boolean isOn = false;
	boolean showFrame = true;
	Rectangle imageRec, textRec;
	String text;
	TrueTypeFont ttFont;
	float maxFontSize, fontScale;
	final float FONTSIZE = 24;
	float[] textColor;
	public enum TEXTLOCATION{UP, DOWN, LEFT, RIGHT};
	TEXTLOCATION textLoc = TEXTLOCATION.UP;
	String keyOn, keyOff;

	GameButton(Rectangle rec, GLTexture tex, float[] textColor, String text, TEXTLOCATION textLoc) {
		super(rec);
		this.textColor = textColor;
		this.text = text;
		this.textLoc = textLoc;
		imageRec = new Rectangle((int)(rec.getX()+rec.getWidth()*0.05), 
				(int)(rec.getY()+rec.getHeight()*0.05), 
				(int)(rec.getWidth()*0.9), (int)(rec.getHeight()*0.9));
		textRec = new Rectangle((int)(rec.getX()+rec.getWidth()*0.05), 
				(int)(rec.getY()+rec.getHeight()*0.05), 
				(int)(rec.getWidth()*0.9), (int)(rec.getHeight()*0.9));
		Font font;
		if(TrueTypeFont.isSupported(LModeller.getGameSetting().getFontName()))
		{
			font = new Font(LModeller.getGameSetting().getFontName(), Font.BOLD, (int)FONTSIZE);
		}
		else
		{
			font = new Font("Arial", Font.BOLD, (int)FONTSIZE);
			System.out.println("Font "+LModeller.getGameSetting().getFontName()+" not supported, using Arial");
		}
		ttFont = new TrueTypeFont(font, true);
		setMaxFontSize(72);
		fontScale = maxFontSize / FONTSIZE;
		setTexture(tex);
	}
	


	public void setToolTipSentence(String sentenceOn, String sentenceOff)
	{
		keyOn = VoicePlayer.getInstance().addTTSVoice(sentenceOn);
		keyOff = VoicePlayer.getInstance().addTTSVoice(sentenceOff);
		setActiveToolTipSentence();
	}
	
	public void toggleOnOff()
	{
		isOn = (isOn)?false:true;
		setActiveToolTipSentence();
	}
	
	public void setOnOff(boolean on)
	{
		isOn = on;
		setActiveToolTipSentence();
	}

	public boolean isOn()
	{
		return isOn;
	}
	
	public void setActiveToolTipSentence()
	{
		if(isOn)
		{
			key = keyOff;
		}
		else
		{
			key = keyOn;
		}
	}
	
	public void paint()
	{
		GL11.glPushMatrix();
    	GL11.glEnable(GL11.GL_TEXTURE_2D);
		if(isOn) 
		{
        	GLApp.setColor(0.8f, 0.65f, 0.0f, 1f);
			fillRect(this.getBounds().getX(), 
					this.getBounds().getY(), this.getBounds().getWidth(), 
					this.getBounds().getHeight());
		}
        GLApp.setColor(textColor);
		if(showFrame) 
		{
			GLApp.drawRect(this.getBounds().getX(), 
					this.getBounds().getY(), this.getBounds().getWidth(), 
					this.getBounds().getHeight());
		}
				
		if(texture!=null && texture.getTextureHandle()!=0)
		{
	        GLApp.setColor(GLApp.colorWhite);
	    	GL11.glEnable(GL11.GL_TEXTURE_2D);
			drawQuad(texture.getTextureHandle(), 
					imageRec.getX(), 
					imageRec.getY(), 
					imageRec.getWidth(), 
					imageRec.getHeight());
		}
		if(text!=null)
		{
	        GLApp.setColor(textColor);
	    	GL11.glEnable(GL11.GL_TEXTURE_2D);
			TrueTypeFont.set2DMode(0, GLApp.getWidth(), 0, GLApp.getHeight());
    		ttFont.drawString(textRec.getX(), textRec.getY(), text, 
    				fontScale, fontScale, TrueTypeFont.ALIGN_LEFT);
			TrueTypeFont.set3DMode();
		}
        GLApp.setColor(GLApp.colorWhite);
        GL11.glPopMatrix();
	}
	
	public int setMaxFontSize(int fontSize)
	{
		if(fontSize<1)
		{
			maxFontSize = 1;
		}
		else
		{
			maxFontSize = fontSize;
		}
		fontScale = maxFontSize / FONTSIZE;
		refreshLocations();
		return (int)(FONTSIZE*fontScale);
	}

	public int setText(String text) {
		fontScale = maxFontSize / FONTSIZE;
		if(text!=null && text.length()>0)
		{
			this.text = text;
		}
		else
		{
			this.text = "";
		}
		refreshLocations();
		return (int)(FONTSIZE*fontScale);
	}
	
	public void showFrame(boolean showFrame)
	{
		this.showFrame = showFrame;
	}
	
	public String getText()
	{
		return this.text;
	}


	public GLTexture getTexture() {
		return texture;
	}


	public void setTexture(GLTexture userTexture) {
		this.texture = userTexture;
		refreshLocations();
	}
	
	protected void refreshLocations()
	{
		if(texture!=null)
		{
			if(text==null)
			{
				if(texture.getWidth() / (float)texture.getHeight() < (rec.getWidth()) / (float)(rec.getHeight()))
				{
					int width = rec.getHeight() * texture.getWidth() / texture.getHeight();
					imageRec.setBounds((int)((rec.getX() + (rec.getWidth()-width)/2)+width*0.05), 
							(int)(rec.getY()+rec.getHeight()*0.05), 
							(int)(width*0.9), (int)(rec.getHeight()*0.9));
				}
				else
				{
					int height = rec.getWidth() * texture.getHeight() / texture.getWidth();
					imageRec.setBounds((int)(rec.getX()+rec.getWidth()*0.05), 
							(int)(rec.getY() + ((rec.getHeight()-height)/2)+height*0.05), 
							(int)(rec.getWidth()*0.9), (int)(height*0.9));
				}
				textRec.setBounds((int)(rec.getX()+rec.getWidth()*0.05), 
						(int)(rec.getY()+rec.getHeight()*0.05), 
						(int)(rec.getWidth()*0.9), (int)(rec.getHeight()*0.9));
			}
			else
			{
				if(textLoc == TEXTLOCATION.UP || textLoc == TEXTLOCATION.DOWN)
				{
					if(rec.getHeight()*.2f<ttFont.getHeight()*fontScale)
					{
						fontScale = rec.getHeight()*.2f/(float)ttFont.getHeight();
					}
					if(rec.getWidth()*.9f<ttFont.getPreciseWidth(text,TrueTypeFont.ALIGN_LEFT)*fontScale)
					{
						fontScale = rec.getWidth()*.9f / (float)ttFont.getPreciseWidth(text,TrueTypeFont.ALIGN_LEFT);
					}
				}
				else
				{
					int maxTextWidth = (int)(rec.getWidth()-rec.getHeight());
					if(maxTextWidth<rec.getHeight()*.5f)
					{
						maxTextWidth = (int)(rec.getHeight()*.5f);
					}
					if(rec.getHeight()*.9f<ttFont.getHeight()*fontScale)
					{
						fontScale = rec.getHeight()*.9f/(float)ttFont.getHeight();
					}
					if(maxTextWidth<ttFont.getPreciseWidth(text,TrueTypeFont.ALIGN_LEFT)*fontScale)
					{
						fontScale = maxTextWidth / (float)ttFont.getPreciseWidth(text,TrueTypeFont.ALIGN_LEFT);
					}
				}
				int textWidth = (int)(ttFont.getPreciseWidth(text,TrueTypeFont.ALIGN_LEFT) * fontScale);
				switch(textLoc)
				{
				case UP:
					if(texture.getWidth() / (float)texture.getHeight() < (rec.getWidth()) / (float)(rec.getHeight() * .75f))
					{
						int width = rec.getHeight() * texture.getWidth() / texture.getHeight();
						imageRec.setBounds((int)((rec.getX() + (rec.getWidth()-width)/2)+width*0.05), 
								(int)(rec.getY()+rec.getHeight()*0.05), 
								(int)(width*0.9), (int)(rec.getHeight()*0.7));
					}
					else
					{
						int height = rec.getWidth() * texture.getHeight() / texture.getWidth();
						imageRec.setBounds((int)(rec.getX()+rec.getWidth()*0.05), 
								(int)(rec.getY() + ((rec.getHeight() * .75f-height)/2)+height*0.05), 
								(int)(rec.getWidth()*0.9), (int)(height*0.7));
					}
					textRec.setBounds((int)(rec.getX()+(rec.getWidth()-textWidth)/2), 
							(int)(rec.getY()+rec.getHeight()*0.75), 
							textWidth, (int)(rec.getHeight()*0.2));
					break;
				case DOWN:
					if(texture.getWidth() / (float)texture.getHeight() < (rec.getWidth()) / (float)(rec.getHeight() * .75f))
					{
						int width = (int)(rec.getHeight() * .75f * texture.getWidth() / texture.getHeight());
						imageRec.setBounds((int)((rec.getX() + (rec.getWidth()-width)/2)+width*0.05), 
								(int)(rec.getY()+rec.getHeight()*0.25), 
								(int)(width*0.9), (int)(rec.getHeight()*0.7));
					}
					else
					{
						int height = rec.getWidth() * texture.getHeight() / texture.getWidth();
						imageRec.setBounds((int)(rec.getX()+rec.getWidth()*0.05), 
								(int)(rec.getY() + ((rec.getHeight() * .75f-height)/2)+rec.getHeight()*0.25), 
								(int)(rec.getWidth()*0.9), (int)(height*0.7));
					}
					textRec.setBounds((int)(rec.getX()+(rec.getWidth()-textWidth)/2), 
							(int)(rec.getY()), 
							textWidth, (int)(rec.getHeight()*0.2));
					break;
				case LEFT:
					if(texture.getWidth() / (float)texture.getHeight() < (rec.getWidth()*0.3) / (float)(rec.getHeight()))
					{
						int width = (int)(rec.getHeight() * texture.getWidth() / texture.getHeight());
						imageRec.setBounds((int)((rec.getX() + (rec.getWidth()-width)/2)+width*0.05), 
								(int)(rec.getY()+rec.getHeight()*0.05), 
								(int)(width*0.9), (int)(rec.getHeight()*0.9));
					}
					else
					{
						int height = (int)(rec.getWidth()*0.3 * texture.getHeight() / texture.getWidth());
						imageRec.setBounds((int)(rec.getX()+rec.getWidth()*0.05), 
								(int)(rec.getY() + ((rec.getHeight()-height)/2)+rec.getHeight()*0.05), 
								(int)(rec.getWidth()*0.3), (int)(height*0.9));
					}
					textRec.setBounds((int)(rec.getX()+(rec.getWidth()-textWidth-imageRec.getWidth())/2), 
							(int)(rec.getY()+rec.getHeight()*0.05), 
							textWidth, (int)(rec.getHeight()*0.9));
					imageRec.setX((int)(rec.getX()+(rec.getWidth()-textWidth-imageRec.getWidth())/2)+textWidth);
					break;
				case RIGHT:
					if(texture.getWidth() / (float)texture.getHeight() < (rec.getWidth()*0.3) / (float)(rec.getHeight()))
					{
						int width = (int)(rec.getHeight() * texture.getWidth() / texture.getHeight());
						imageRec.setBounds((int)((rec.getX() + (rec.getWidth()-width)/2)+width*0.05), 
								(int)(rec.getY()+rec.getHeight()*0.05), 
								(int)(width*0.9), (int)(rec.getHeight()*0.9));
					}
					else
					{
						int height = (int)(rec.getWidth()*0.3 * texture.getHeight() / texture.getWidth());
						imageRec.setBounds((int)(rec.getX()+rec.getWidth()*0.05), 
								(int)(rec.getY() + ((rec.getHeight()-height)/2)+rec.getHeight()*0.05), 
								(int)(rec.getWidth()*0.3), (int)(height*0.9));
					}
					textRec.setBounds((int)(rec.getX()+(rec.getWidth()-textWidth-imageRec.getWidth())/2+imageRec.getWidth()), 
							(int)(rec.getY()+rec.getHeight()*0.05), 
							textWidth, (int)(rec.getHeight()*0.9));
					imageRec.setX((int)(rec.getX()+(rec.getWidth()-textWidth-imageRec.getWidth())/2));
					break;
				}
			}
		}
		else
		{
			imageRec.setBounds((int)(rec.getX()+rec.getWidth()*0.05), 
					(int)(rec.getY()+rec.getHeight()*0.05), 
					(int)(rec.getWidth()*0.9), (int)(rec.getHeight()*0.9));

			if(text==null)
			{
				textRec.setBounds((int)(rec.getX()+rec.getWidth()*0.05), 
						(int)(rec.getY()+rec.getHeight()*0.05), 
						(int)(rec.getWidth()*0.9), (int)(rec.getHeight()*0.9));
			}
			else
			{
				int maxTextWidth = (int)(rec.getWidth()-rec.getHeight());
				if(maxTextWidth<rec.getHeight()*.5f)
				{
					maxTextWidth = (int)(rec.getHeight()*.5f);
				}
				if(rec.getHeight()*.9f<ttFont.getHeight()*fontScale)
				{
					fontScale = rec.getHeight()*.9f/(float)ttFont.getHeight();
				}
				if(maxTextWidth<ttFont.getPreciseWidth(text,TrueTypeFont.ALIGN_LEFT)*fontScale)
				{
					fontScale = maxTextWidth / (float)ttFont.getPreciseWidth(text,TrueTypeFont.ALIGN_LEFT);
				}
				int textWidth = (int)(ttFont.getPreciseWidth(text,TrueTypeFont.ALIGN_LEFT) * fontScale);
				int textHeight = (int)(ttFont.getHeight() * fontScale);
				textRec.setBounds((int)(rec.getX()+(rec.getWidth()-textWidth)/2), 
						(int)(rec.getY()+(rec.getHeight()-textHeight)/2), 
						textWidth, textHeight);
			}
		}
	}
}
